import Draggable from 'vuedraggable'
import './index.less'
import store from '@/store'
import config from '@/config'
/**
 * 上传文件
 */
export default {
  name: 'Upload',
  components: {
    Draggable
  },
  props: {
    action: {
      type: String,
      default: config.api.uploadURL
    },  // 上传源
    accept: {
      type: String,
      default: config.upload.image.accept
    },  // 文件类型   
    multiple: {
      type: Boolean,
      default: false
    },  // 支持多选
    limit: {
      type: Number,
      default: 1
    },  // 最大上传
    list: {
      type: Array,
      default: () => {
        return []
      }
    },  // 已有图片集合
    tips: {
      type: String,
      default: config.upload.image.tips
    },  // 提醒文本
    headers: {
      type: Object,
      default: () => {
        return {
          Authorization: `Bearer ${store.state.auth.token}`
        }
      }
    },  // 请求头
  },
  data() {
    return {
      loading: false, // 加载状态
    }
  },
  methods: {
    setLoading(flag) {
      this.loading = flag
    },
    // 上传成功
    onSuccess(res) {
      this.setLoading(false)
      const url = config.api.imageURL + res.data.url
      const arr = [...this.list, url]
      this.$emit('success', arr)
    },
    // 上传失败
    onError(err) {
      this.setLoading(false)
      try {
        const errMsg = JSON.parse(err.message)
        this.$message.error(errMsg.message ? errMsg.message : '上传文件失败')
      } catch(error) {
        this.$message.error('上传文件失败')
      }
    },
    // 上传之前
    beforeUpload(file) {
      // 校验文件大小
      this.setLoading(true)
      this.$emit('before', file)
    },
    // 替换文件
    updateFile(res, index) {
      this.setLoading(false)
      const url = config.api.imageURL + res.data.url
      let arr = [...this.list]
      arr[index] = url
      this.$emit('success', arr)
    },
    // 删除文件
    deleteFile(index) {
      let arr = [...this.list]
      arr.splice(index, 1)
      this.$emit('success', arr)
    },
    // 文件排序
    sortFile(arr) {
      this.$emit('success', arr)
    },
    // 超出限制
    onExceed() {
      this.$message.error('超出限制大小')
    },
  },
  render(h) {
    // 上传器
    const Uploader = (ctx) => {
      const { props, children } = ctx
      const { customClass, index } = props
      // 上传成功
      const uploadSuccess = (res) => {
        // 替换
        if (index >= 0) {
          this.updateFile(res, index)
          return
        }
        // 上传
        this.onSuccess(res)
      }
      return (
        <el-upload
          class={customClass}
          limit={this.limit}
          show-file-list={false}
          multiple={this.multiple}
          action={this.action}
          accept={this.accept}
          headers={this.headers}
          before-upload={this.beforeUpload}
          drag
          props={
            {
              onSuccess: uploadSuccess,
              onError: this.onError,
              onExceed: this.onExceed
            }
          }
        >
          {children}
        </el-upload> 
      )
    }
    // 文件列表
    const FileList = () => {
      return (
        <div class="file-list flex">
          {
            <Draggable
              class="flex flex-warp"
              value={this.list}
              onInput={this.sortFile}
              group="upload"
              onStart={(drag) => drag = true}
              onEnd={(drag) => drag = false}
              options={{ chosenClass: 'choose', animation: 150, draggable: '.can-move' }}
            >
              {
                this.list.map((v, i) => (
                  <div class="file-item size can-move">
                      {
                        this.accept === 'video/mp4'
                        ?
                        <video class="avatar" src={v} />
                        :
                        <el-image class="avatar" src={v} fit="contain" />
                      }
                      <div class="handle-bar flex flex-align-center gesture--click">
                        <Uploader custom-class="handle-btn flex-1" index={i}>
                          <i class="el-icon-edit-outline">更换</i>
                        </Uploader>
                        <i class="el-icon-delete handle-btn flex-1 gesture--click" onClick={() => this.deleteFile(i)}>删除</i>
                      </div>
                  </div>
                ))
              }
              {
                this.list.length < this.limit
                &&
                <Uploader custom-class="avatar-uploader file-item size">
                  <i class="el-icon-plus size avatar-uploader-icon flex flex-just-center flex-align-center" />
                </Uploader>
              }
            </Draggable>
          }
        </div>
      )
    }
    // 提示
    const Tip = () => {
      return (<p class="tip">{this.tips}</p>)
    }

    return (
      <div class="upload">
        <FileList />
        <Tip />
      </div>
    )
  }
}